﻿using Microsoft.EntityFrameworkCore;

namespace Sgr.EntityFrameworkCore
{
    public static class DbContextOptionsBuilderExtensions
    {
        //具体配置可参考  https://learn.microsoft.com/zh-cn/ef/core/logging-events-diagnostics/

        public static DbContextOptionsBuilder ConfigureLoggingAndErrors(
            this DbContextOptionsBuilder builder,
            IServiceProvider serviceProvider)
        {
            // 通过下面的代码，我们可以配置特殊的日志类型
            //var loggerFactory = LoggerFactory.Create(builder =>
            //{
            //    builder
            //        .AddFilter("Microsoft", LogLevel.Warning) // 过滤系统日志
            //        .AddFilter("System", LogLevel.Warning)
            //        .AddFilter("Microsoft.EntityFrameworkCore.Database.Command", LogLevel.Warning); // 仅记录 SQL
            //});
            //builder.UseLoggerFactory(loggerFactory);

            /*
             * EnableSensitiveDataLogging
             *
             *  默认情况下，EF Core 不会在异常消息中包含任何数据的值。 这是因为这些数据可能是机密数据，如果不处理异常，可能会在生产使用中泄露这些数据
             *  EnableSensitiveDataLogging 方法可以启用敏感数据日志记录，这在调试和诊断问题时非常有用，但在生产环境中应谨慎使用，以避免泄露敏感信息
             *
             * EnableDetailedErrors
             *
             *  出于性能原因，EF Core 不会在 try-catch 块中包装每个调用以从数据库提供程序读取值。 但是，这有时会导致难以诊断的异常，尤其是当数据库在模型不允许的情况下返回 NULL 时。
             *  启用 EnableDetailedErrors 将导致 EF 引入这些 try-catch 块，从而提供更详细的错误
             *
             * 更改事件的日志级别
             *
             *  有时，更改事件的预定义日志级别可能会很有用。 例如:
             *      可用于将两个附加事件从 LogLevel.Debug 提升到 LogLevel.Information
             *      禁止记录每某个事件
             *      等等
             */
#if DEBUG
            builder
                .EnableSensitiveDataLogging()
                .EnableDetailedErrors();

            //builder.ConfigureWarnings(
            //                b =>
            //                {
            //                    //将两个附加事件从 LogLevel.Debug 提升到 LogLevel.Information
            //                    b.Log(
            //                    (RelationalEventId.ConnectionOpened, LogLevel.Information),
            //                    (RelationalEventId.ConnectionClosed, LogLevel.Information));

            //                    //禁止记录每某个事件
            //                    b.Ignore(CoreEventId.DetachedLazyLoadingWarning);

            //                    //针对事件引发异常
            //                    b.Throw(RelationalEventId.QueryPossibleUnintendedUseOfEqualsWarning);
            //                });

            //// 注册拦截器
            //// 慢查询拦截器
            ////（其实也可以进行日志分析来获取慢查询，EF Core 的 SQL 执行日志（Microsoft.EntityFrameworkCore.Database.Command）会记录每条 SQL 的执行时间）
            //try
            //{
            //    var loggerFactory = serviceProvider.GetRequiredService<ILoggerFactory>();
            //    builder.AddInterceptors(new SlowQueryInterceptor(
            //        loggerFactory.CreateLogger<SlowQueryInterceptor>()));

            //    builder.UseLoggerFactory(loggerFactory);
            //}
            //catch (Exception ex)
            //{
            //    // 记录错误但允许应用继续运行
            //    // 如果 logger 获取失败，不应该影响数据库配置的其他部分
            //    System.Diagnostics.Debug.WriteLine($"Failed to configure logging: {ex.Message}");
            //}

#endif

            return builder;
        }
    }
}